package cmd

import (
	"bytes"
	"errors"
	"fmt"
	"os"
	"os/exec"
	"os/user"
	"runtime"
	"strings"

	"gitee.com/shaddy/k3sinstall/mylog"
	"github.com/spf13/cobra"
)

const (
	ErrorExitOSCase = -1
)

var (
	rootCmd    = &cobra.Command{Use: "k3sinstall"}
	ConfigHome string
	ConfigFile string
)

func Execute() error {
	return rootCmd.Execute()
}

func init() {
	cobra.OnInitialize(initConfig)
	rootCmd.AddCommand(initCmd)
	rootCmd.AddCommand(versionCmd)
	rootCmd.AddCommand(cleanCmd)
	rootCmd.AddCommand(addCmd)
	rootCmd.AddCommand(imageCmd)

}

func FileExist(path string) bool {
	_, err := os.Stat(path)
	return err == nil || os.IsExist(err)
}

// initConfig reads in config file and ENV variables if set.
func initConfig() {
	// Find home directory.
	home, err := Home()
	if err != nil {
		mylog.Error.Panicf("获取Home目录失败 %s", err.Error())
	}
	ConfigHome = home
	if !FileExist(home + "/.k3sinstall") {
		err := os.MkdirAll(home+"/.k3sinstall", os.ModePerm)
		if err != nil {
			fmt.Println("create default k3sinstall config dir failed, please create it by your self mkdir -p /root/.k3sinstall && touch /root/.k3sinstall/config.yaml")
		}
	}
	ConfigFile = home + "/.k3sinstall/config.yaml"
}

func Home() (string, error) {
	user, err := user.Current()
	if nil == err {
		return user.HomeDir, nil
	}
	// cross compile support
	if "windows" == runtime.GOOS {
		return homeWindows()
	}
	// Unix-like system, so just assume Unix
	return homeUnix()
}

func homeUnix() (string, error) {
	// First prefer the HOME environmental variable
	if home := os.Getenv("HOME"); home != "" {
		return home, nil
	}
	// If that fails, try the shell
	var stdout bytes.Buffer
	cmd := exec.Command("sh", "-c", "eval echo ~$USER")
	cmd.Stdout = &stdout
	if err := cmd.Run(); err != nil {
		return "", err
	}
	result := strings.TrimSpace(stdout.String())
	if result == "" {
		return "", errors.New("blank output when reading home directory")
	}
	return result, nil
}

func homeWindows() (string, error) {
	drive := os.Getenv("HOMEDRIVE")
	path := os.Getenv("HOMEPATH")
	home := drive + path
	if drive == "" || path == "" {
		home = os.Getenv("USERPROFILE")
	}
	if home == "" {
		return "", errors.New("HOMEDRIVE, HOMEPATH, and USERPROFILE are blank")
	}
	return home, nil
}
